#include "sserver.h"
#include "CinUserMap.h"
#include "utils/Utils.h"
#include "business/UserSevice.h"
#include "business/MessageSevice.h"
#include "business/LiveSevice.h"
#include "business/FileSevice.h"
#include "threadpool/CSeviceJob.h"
#include "threadpool/CHandleJob.h"
#include "SocketHandle.h"


SServer *SServer::mInstance = NULL;

SServer *SServer::GetInstance()
{
    if (!mInstance)
    {
        mInstance = new SServer();
    }
    return mInstance;
}

SServer::SServer()
    : listener(-1)
{
    mSocket = new Socket();
}

SServer::~SServer()
{
    delete mSocket;
    delete mEpoll;
    delete mThreadmanager;
}
int SServer::init(int port)
{
    if (mSocket->create(this))
    {
        std::cout << " Socket created\n";
        mSocket->bind(port);
        listener = mSocket->listen();
        mSocket->set_non_blocking(listener, true);
        mEpoll = new EpollHandle(listener, this);
        mEpoll->epoll_add_fd(listener);
        mThreadmanager = new CThreadManage(1024, 10, 100, 50);
    }
    std::cout << "SServer init finish\n";
}

void SServer::doCirculate()
{
    while (1)
    {
        mEpoll->epoll_do_wait();
        mEpoll->epoll_handle();
    }
    ::close(listener);
    mEpoll->epoll_close();
    mThreadmanager->TerminateAll();
}

void SServer::SetStatus(SocketStatus status)
{
}

int SServer::Send(const char *data, int len)
{
}

//处理客户端数据
void SServer::OnHandleData(int peerfd, int tag)
{   
    if (tag == 1)
    { //处理接入的客户端
        int clinet = mSocket->accept(peerfd);
        mSocket->set_non_blocking(clinet, true);
        mEpoll->epoll_add_fd(clinet);
        long time = Utils::getCurTime();
        CinUserMap::GetInstance()->addClient(clinet, time);       
    }
    else
    { //其他客户端活动业务处理
        cout << " SS OnHandleData to " << peerfd << endl;
        // SocketHandle *sHandle = new SocketHandle();
        // sHandle->setObserver(this);
        // CHandleJob  *job=new CHandleJob(peerfd);
        // job->setSocket(sHandle);
        // mThreadmanager->Run(job, (void *)&peerfd);
       int ret = mSocket->doRecv(peerfd);
       if(ret == -2){///检测到客户端判开处理
          mEpoll->epoll_del_fd(peerfd);
          mSocket->closeFd(peerfd);
          CinUserMap::GetInstance()->removeMap(peerfd);
       }
   
    }
}

void SServer::RevData(const int fd, const unsigned short &nOpcode, const char *pDataBuffer, unsigned short nDataSize)
{
    cout << "nOpcode :" << nOpcode << endl;
    switch (nOpcode)
    {
    case NET_LOGIN:
    {
        NetPacket_Login *pMsg = (NetPacket_Login *)pDataBuffer;
        NetPacket_Login msg;        
        strncpy(msg.uid, pMsg->uid, sizeof(msg.uid));
        strncpy(msg.arrMessage, pMsg->arrMessage, sizeof(msg.arrMessage));
               
        UserSevice *uService = new UserSevice();
        uService->setObserver(this);
        uService->setSocket(mSocket);
        uService->setPeerfd(fd);
       
        CSeviceJob *job=new CSeviceJob();
        job->SetSevice(uService);
        mThreadmanager->Run(job, (void *)&msg);
    }
    break;
    case NET_VIDEO:
    {
        NetPacket_VideoBuf *pData = (NetPacket_VideoBuf *)pDataBuffer;
        NetPacket_VideoBuf vData;
        vData.flag = pData->flag;
        vData.count = pData->count;
        strncpy(vData.from, pData->from, sizeof(vData.from));
        strncpy(vData.to, pData->to, sizeof(vData.to));
        strncpy(vData.buf, pData->buf, sizeof(vData.buf));

        std::cout << "==pData->count= " << pData->count<<endl;
        sendAll(fd, NET_VIDEO, (const char*)&vData, sizeof(vData));
    }
    break;
    case NET_MSG:
    {
        NetPacket_MsgData *pData = (NetPacket_MsgData *)pDataBuffer;
        NetPacket_MsgData vData;
        vData.flag = pData->flag;
        strncpy(vData.msgid, pData->msgid, sizeof(vData.msgid));
        strncpy(vData.from, pData->from, sizeof(vData.from));
        strncpy(vData.to, pData->to, sizeof(vData.to));
        strncpy(vData.sendMessage, pData->sendMessage, sizeof(vData.sendMessage));
        
        MessageSevice *mSevice = new MessageSevice();
        mSevice->setObserver(this);
        mSevice->setSocket(mSocket);
        mSevice->setPeerfd(fd);

        CSeviceJob *job=new CSeviceJob();
        job->SetSevice(mSevice);
        mThreadmanager->Run(job, (void *)&vData);
    }
    break;
    case NET_TIMELIVE:
    {
        NetPacket_TimeLive *pData = (NetPacket_TimeLive *)pDataBuffer;
        NetPacket_TimeLive vData;
        
        strncpy(vData.uid, pData->uid, sizeof(vData.uid));

        LiveSevice *mSevice = new LiveSevice();
        mSevice->setObserver(this);
        mSevice->setSocket(mSocket);
        mSevice->setPeerfd(fd);

        CSeviceJob *job=new CSeviceJob();
        job->SetSevice(mSevice);
        mThreadmanager->Run(job, (void *)&vData);
    }
    break;
    case NET_FILE:
    {
        // NetPacket_File *pData = (NetPacket_File *)pDataBuffer;
        // NetPacket_File vData;
        
        // strncpy(vData.uid, pData->uid, sizeof(vData.uid));

        FileSevice *mSevice = new FileSevice();
        mSevice->setObserver(this);
        mSevice->setSocket(mSocket);
        mSevice->setPeerfd(fd);

        CSeviceJob *job=new CSeviceJob();
        job->SetSevice(mSevice);
        mThreadmanager->Run(job, (void *)pDataBuffer);
    }
    break;
    default:
    {
        std::cout << "other :" << nOpcode << std::endl;
       
    }
    break;
    }
}

void SServer::sendAll(const int peerfd,const unsigned short &nOpcode, const char *pDataBuffer, unsigned short nDataSize)
{
//    // int cnt = clients_list.size();
//     list<int>::iterator it;    
   
//     for(it = clients_list.begin(); it != clients_list.end() ; it++)
//     { 
//         int fd = *it;
//         if(fd == peerfd){
//             continue;
//         }
       
//         mSocket->send(fd, nOpcode, pDataBuffer, nDataSize);
//     }
}

void SServer::OnSeviceCallback(int a, int b)
{
   ;
}